package com.github.wxpay.sdk;

import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.math.BigDecimal;
import java.net.ConnectException;
import java.net.URL;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.zip.GZIPInputStream;
import java.util.zip.GZIPOutputStream;

import javax.net.ssl.HttpsURLConnection;

import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.io.SAXReader;

import com.alibaba.fastjson.JSON;

import bill.Bill;
import bill.BillAll;
import bill.WX;
import hyl.core.MyCharset;
import hyl.core.io.MyFile;
import hyl.core.run.IDo;
import hyl.core.run.IDoEach;

public class WXPayHttp {
	
	public static String url = "https://api.mch.weixin.qq.com/pay/downloadbill";
	public static String appid;
    public static String mch_id;// "1542819161";
    public static String nonce_str;
    public static String sign;//可选
    public static int bill_date;
    public static String bill_type = "ALL";
    public static String key;
    
    public WXPayHttp(WX wx) throws Exception{
    	appid=wx.getAppid();
    	mch_id=wx.getMch_id();
    	nonce_str=WXPayUtil.generateNonceStr();
    	bill_date=wx.getBill_date();
    	key=wx.getKey();
    }
    
    public static String GetSignString() throws Exception {
    	Map map = new HashMap();
    	map.put("appid", appid);
    	map.put("bill_date", String.valueOf(bill_date));
    	map.put("bill_type", bill_type);
    	map.put("mch_id", mch_id);
    	map.put("nonce_str", nonce_str);
    	//map.put("tar_type", "GZIP");
    	return WXPayUtil.generateSignature(map,key);
    }
    
    public Map httpclient() throws Exception {
    	Map map = new HashMap();
    	map.put("appid", appid);
    	map.put("bill_date", String.valueOf(bill_date));
    	map.put("bill_type", bill_type);
    	map.put("mch_id", mch_id);
    	map.put("nonce_str", nonce_str);
    	map.put("sign", WXPayHttp.GetSignString());
    //	map.put("tar_type", "GZIP");
    	Map mp = httpsRequest(url, "POST", WXPayUtil.mapToXml(map));
    	return mp;
    }
    
    public static Map httpsRequest(String requestUrl, String requestMethod, String outputStr){
    	final List<Bill> list = new ArrayList<Bill>();
    	final Map map = new HashMap();
        try {
            URL url = new URL(requestUrl);
            HttpsURLConnection conn = (HttpsURLConnection) url.openConnection();
            conn.setDoOutput(true);
            conn.setDoInput(true);
            conn.setUseCaches(false);
            // 设置请求方式（GET/POST）
            conn.setRequestMethod(requestMethod);
            conn.setRequestProperty("content-type", "application/x-www-form-urlencoded");
            // 当outputStr不为null时向输出流写数据
            if (null != outputStr) {
                OutputStream outputStream = conn.getOutputStream();
                // 注意编码格式
                outputStream.write(outputStr.getBytes("UTF-8"));
                outputStream.close();
            }
            // 从输入流读取返回内容
            InputStream inputStream = conn.getInputStream();
            
            String asxml = asxml(inputStream);
            if(asxml.length()>0||!asxml.isEmpty()) {
            	Map mmp = WXPayUtil.xmlToMap(asxml);
            	mmp.put("code", 0);
            	return mmp;
            }
            
            MyFile.readLineByEach(inputStream, MyCharset.UTF8, new IDoEach<String>(){
            long x;
			public boolean run(long index, String obj) {
				if(index==0)return false;
				if(obj.startsWith("总")) {
					x=index;
					return false;
				}
				if(index==x+1) {
					map.put("map", GetAllData(obj));
					return false;
				}
				list.add(analyze(obj));
				return false;
			}
          });
            
            inputStream.close();
            inputStream = null;
            conn.disconnect();
            map.put("list", list);
            map.put("code", 1);
        } catch (ConnectException ce) {
            System.out.println("连接超时：{}");
        } catch (Exception e) {
            System.out.println("https请求异常：{}");
        }
        return map;
    }
    
    //截取详细信息
    public static Bill analyze(String data){
        	String[] order = data.split(","); //通过交易时间分隔   订单数
            Bill bill = new Bill();
            bill.setDate(order[0].replace("`", ""));
            bill.setAppId(order[1].replace("`", ""));
            bill.setMch_id(order[2].replace("`", ""));
            bill.setSubMch_id(order[3].replace("`", ""));
            bill.setDevice_info(order[4].replace("`", ""));
            bill.setWeiXinOrderNo(order[5].replace("`", ""));
            bill.setMchOrderNo(order[6].replace("`", ""));
            bill.setUserId(order[7].replace("`", ""));
            bill.setType(order[8].replace("`", ""));
            bill.setStatus(order[9].replace("`", ""));
            bill.setBank(order[10].replace("`", ""));
            bill.setCurrency(order[11].replace("`", ""));
            bill.setSdmoney(order[12].replace("`", ""));
            bill.setDjmoney(order[13].replace("`", ""));
            bill.setBackOrderNo(order[14].replace("`", ""));
            bill.setShopOrderNo(order[15].replace("`", ""));
            bill.setBackmoney(order[16].replace("`", ""));
            bill.setBackrecharge(order[17].replace("`", ""));
            bill.setBacktype(order[18].replace("`", ""));
            bill.setBackstutas(order[19].replace("`", ""));
            bill.setGoodname(order[20].replace("`", ""));
            bill.setShopdata(order[21].replace("`", ""));
            bill.setFee(order[22].replace("`", ""));
            bill.setFeerate(order[23].replace("`", ""));
            bill.setOrdermoney(order[24].replace("`", ""));
            bill.setApplyback(order[25].replace("`", ""));
            bill.setFeeremark(order[26].replace("`", ""));
        return bill;
    }
    
    
    //截取统计数据
    public static BillAll GetAllData(String data) {
    	String[] order = data.split(","); 
    	BillAll bill = new BillAll();
    	bill.setTradeall(order[0].replace("`", ""));
    	bill.setTrademoney(order[1].replace("`", ""));
    	bill.setBackall(order[2].replace("`", ""));
    	bill.setChongzhiall(order[3].replace("`", ""));
    	bill.setFeeall(order[4].replace("`", ""));
    	bill.setOrderall(order[5].replace("`", ""));
    	bill.setApplybackall(order[6].replace("`", ""));
    	return bill;
    }
    
    //解压
    public static byte[] uncompress(byte[] bytes) {
        if (bytes == null || bytes.length == 0) {
            return null;
        }
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        ByteArrayInputStream in = new ByteArrayInputStream(bytes);
        try {
            GZIPInputStream ungzip = new GZIPInputStream(in);
            byte[] buffer = new byte[256];
            int n;
            while ((n = ungzip.read(buffer)) >= 0) {
                out.write(buffer, 0, n);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return out.toByteArray();
    }
    //压缩
    public static byte[] compress(String str, String encoding) {
        if (str == null || str.length() == 0) {
            return null;
        }
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        GZIPOutputStream gzip;
        try {
            gzip = new GZIPOutputStream(out);
            gzip.write(str.getBytes(encoding));
            gzip.close();
        } catch ( Exception e) {
            e.printStackTrace();
        }
        return out.toByteArray();
    }
    
    public static void saveFile(String filename,byte [] data)throws Exception{   
        if(data != null){   
          String filepath ="E:\\" + filename;   
          File file  = new File(filepath);   
          if(file.exists()){   
             file.delete();   
          }   
          FileOutputStream fos = new FileOutputStream(file);   
          fos.write(data,0,data.length);   
          fos.flush();   
          fos.close();   
        }   
    }
    
    /**
     * 判断是否为xml字符串
     * 
     * */
    public static String asxml(InputStream inputStream) {
    	SAXReader saxReader = new SAXReader();
    	try {
			Document tempDocument = saxReader.read(inputStream);
			return tempDocument.asXML();
		} catch (DocumentException e) {
			return "";
		}
    }
}

